package org.pupil.queue;

/**
 * @Description: 循环双端队列：数组实现方式  leetcode：https://leetcode.cn/problems/design-circular-deque/description/
 * @Author: pupil
 * @Date: 2024/08/05 下午 2:52
 */
public class MyCircularDeque {
    private int[] deque;
    private int l, r, size, limit;

    // 双端队列最大为 k
    public MyCircularDeque(int k) {
        deque = new int[k];
        l = r = size = 0;
        limit = k;
    }

    // 将一个元素添加到双端队列头部
    // l == 0 时，入 limit-1 位置，l = limit-1
    // l != 0 时，入 l-1 位置，l = l-1
    public boolean insertFront(int value) {
        if (isFull()) {
            return false;
        } else {
            if (isEmpty()) {
                l = r = 0;
                deque[0] = value;
            } else {
                l = l == 0 ? (limit - 1) : (l - 1);
                deque[l] = value;
            }
            size++;
            return true;
        }
    }

    // 将一个元素添加到双端队列尾部
    // r == limit-1 时，入 0 位置，r = 0
    // r != limit-1 时，入 r+1 位置，r = r+1
    public boolean insertLast(int value) {
        if (isFull()) {
            return false;
        } else {
            if (isEmpty()) {
                l = r = 0;
                deque[0] = value;
            } else {
                r = r == (limit - 1) ? 0 : (r + 1);
                deque[r] = value;
            }
            size++;
            return true;
        }
    }

    // 从双端队列头部删除一个元素
    // l == limit-1 时，删除元素后，l = 0
    // l != limit-1时，删除元素后，l = l+1
    public boolean deleteFront() {
        if (isEmpty()) {
            return false;
        } else {
            l = l == (limit - 1) ? 0 : l + 1;
            size--;
            return true;
        }
    }

    // 从双端队列尾部删除一个元素
    // r == 0 时，删除元素后，r = limit-1
    // r !=0 时，删除元素后，r = r-1
    public boolean deleteLast() {
        if (isEmpty()) {
            return false;
        } else {
            r = r == 0 ? (limit - 1) : r - 1;
            size--;
            return true;
        }
    }

    // 从双端队列头部获得一个元素
    public int getFront() {
        if (isEmpty()){
            return -1;
        }else {
            return deque[l];
        }
    }

    // 获得双端队列的最后一个元素
    public int getRear() {
        if (isEmpty()){
            return -1;
        }else {
            return deque[r];
        }
    }

    // 判断队列是否为空
    public boolean isEmpty() {
        return size == 0;
    }

    // 判断队列是否为满
    public boolean isFull() {
        return size == limit;
    }
}
